package com.xyht.medicine_management_system.modules.consumptionPoint.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.xyht.medicine_management_system.common.commonReturn.CommonCodeEnum;
import com.xyht.medicine_management_system.common.commonReturn.CommonResult;
import com.xyht.medicine_management_system.common.commonReturn.ResponseResult;
import com.xyht.medicine_management_system.modules.consumptionPoint.entity.MmsConsumptionPointRule;
import com.xyht.medicine_management_system.modules.consumptionPoint.entity.req.MmsConsumptionPointRuleReq;
import com.xyht.medicine_management_system.modules.consumptionPoint.entity.resp.MmsConsumptionPointRuleResp;
import com.xyht.medicine_management_system.modules.consumptionPoint.mapper.MmsConsumptionPointRuleMapper;
import com.xyht.medicine_management_system.modules.consumptionPoint.service.MmsConsumptionPointRuleService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

import static com.xyht.medicine_management_system.common.util.ParamCheckUtil.isNullOrEmpty;
import static com.xyht.medicine_management_system.modules.consumptionPoint.constant.PointRuleStatusConstant.POINT_RULE_STATUS_ENABLE;

/**
 * <p>
 * 积分规则表 服务实现类
 * </p>
 *
 * @author XYHT
 * @since 2023-12-06
 */
@Service
public class MmsConsumptionPointRuleServiceImpl extends ServiceImpl<MmsConsumptionPointRuleMapper, MmsConsumptionPointRule> implements MmsConsumptionPointRuleService {

    @Override
    public ResponseResult addConsumptionPointRule(MmsConsumptionPointRuleReq ruleReq, String userId) {
        if (isNullOrEmpty(ruleReq.getPointsRate(), ruleReq.getName(), ruleReq.getStartDate(), ruleReq.getEndDate(), ruleReq.getStatus())) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        if (ruleReq.getPointsRate() <= 0) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        Date nowDate = new Date();
        if (nowDate.before(ruleReq.getStartDate()) || ruleReq.getStartDate().after(ruleReq.getEndDate())) {
            return CommonResult.failed(CommonCodeEnum.TIME_ILLEGAL);
        }

        //若为启用状态,先查询持续时间是否有冲突
        if (ruleReq.getStatus() == POINT_RULE_STATUS_ENABLE) {
            List<MmsConsumptionPointRule> defaultRuleList = this.list(new LambdaQueryWrapper<MmsConsumptionPointRule>()
                    .eq(MmsConsumptionPointRule::getStatus, POINT_RULE_STATUS_ENABLE)//启用状态
                    .between(MmsConsumptionPointRule::getStartDate, ruleReq.getStartDate(), ruleReq.getEndDate())
                    .or()
                    .between(MmsConsumptionPointRule::getEndDate, ruleReq.getStartDate(), ruleReq.getEndDate()));
            //若存在冲突
            if (!defaultRuleList.isEmpty()) {
                return CommonResult.failed(CommonCodeEnum.POINT_RULE_TIME_CONFLICT);
            }
        }

        //添加本积分规则
        MmsConsumptionPointRule rule = new MmsConsumptionPointRule();
        BeanUtils.copyProperties(ruleReq, rule);
        rule.setCreatorId(userId);
        this.save(rule);

        return CommonResult.success();
    }

    @Override
    public ResponseResult updateConsumptionPointRule(MmsConsumptionPointRuleReq ruleReq) {
        if (isNullOrEmpty(ruleReq.getId())) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        if (!isNullOrEmpty(ruleReq.getPointsRate())) {
            if (ruleReq.getPointsRate() <= 0) {
                return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
            }
        }

        if (!isNullOrEmpty(ruleReq.getStartDate(), ruleReq.getEndDate())) {
            Date nowDate = new Date();
            if (nowDate.before(ruleReq.getStartDate()) || ruleReq.getStartDate().after(ruleReq.getEndDate())) {
                return CommonResult.failed(CommonCodeEnum.TIME_ILLEGAL);
            }
        }

        MmsConsumptionPointRule rule = this.getById(ruleReq.getId());
        if (isNullOrEmpty(rule)) {
            return CommonResult.failed(CommonCodeEnum.POINT_RULE_NOT_EXIST);
        }

        //若为启用状态,先查询持续时间是否有冲突
        if (ruleReq.getStatus() == POINT_RULE_STATUS_ENABLE) {
            List<MmsConsumptionPointRule> defaultRuleList = this.list(new LambdaQueryWrapper<MmsConsumptionPointRule>()
                    .eq(MmsConsumptionPointRule::getStatus, POINT_RULE_STATUS_ENABLE)//启用状态
                    .ne(MmsConsumptionPointRule::getId, rule.getId())//排除自身
                    .and(i -> i.between(MmsConsumptionPointRule::getStartDate, ruleReq.getStartDate(), ruleReq.getEndDate())
                            .or()
                            .between(MmsConsumptionPointRule::getEndDate, ruleReq.getStartDate(), ruleReq.getEndDate())));
            //若存在冲突
            if (!defaultRuleList.isEmpty()) {
                return CommonResult.failed(CommonCodeEnum.POINT_RULE_TIME_CONFLICT);
            }
        }

        //修改该条规则
        MmsConsumptionPointRule updRule = new MmsConsumptionPointRule();
        BeanUtils.copyProperties(ruleReq, updRule);
        this.updateById(updRule);

        return CommonResult.success();
    }

    @Override
    public ResponseResult listConsumptionPointRule(Integer pageNum, Integer pageSize, Date startDate, Date endDate, Integer status, String searchStr) {
        LambdaQueryWrapper<MmsConsumptionPointRule> queryWrapper = new LambdaQueryWrapper<MmsConsumptionPointRule>()
                .orderByDesc(MmsConsumptionPointRule::getCreateTime);
        //在时间段内
        if (!isNullOrEmpty(startDate, endDate)) {
            queryWrapper.between(MmsConsumptionPointRule::getStartDate, startDate, endDate)
                    .or()
                    .between(MmsConsumptionPointRule::getEndDate, startDate, endDate);
        }
        //规则启用状态
        if (!isNullOrEmpty(status)) {
            queryWrapper.eq(MmsConsumptionPointRule::getStatus, status);
        }
        if (!isNullOrEmpty(searchStr)) {
            StringUtils.deleteWhitespace(searchStr);
            queryWrapper.like(MmsConsumptionPointRule::getName, searchStr).or()
                    .like(MmsConsumptionPointRule::getStatus, searchStr).or()
                    .like(MmsConsumptionPointRule::getNote, searchStr);
        }

        Page<MmsConsumptionPointRule> page = new Page<>(pageNum, pageSize);
        this.page(page, queryWrapper);

        List<MmsConsumptionPointRuleResp> ruleRespList = page.getRecords().stream().map(rule -> {
            MmsConsumptionPointRuleResp ruleResp = new MmsConsumptionPointRuleResp();
            BeanUtils.copyProperties(rule, ruleResp);
            return ruleResp;
        }).collect(Collectors.toList());

        return CommonResult.success(ruleRespList, (int) page.getTotal());
    }

    @Override
    public ResponseResult ruleDetail(String ruleId) {
        if (isNullOrEmpty(ruleId)) {
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        MmsConsumptionPointRule rule = this.getById(ruleId);
        if (isNullOrEmpty(rule)) {
            return CommonResult.failed(CommonCodeEnum.POINT_RULE_NOT_EXIST);
        }

        MmsConsumptionPointRuleResp ruleResp = new MmsConsumptionPointRuleResp();
        BeanUtils.copyProperties(rule, ruleResp);

        return CommonResult.success(ruleResp);
    }
}
